import path from "path";

// 把mock配置文件展开成route
function createRoute(mockConfList) {
  let mockRouteMap = {};
  mockConfList.forEach((mockConf) => {
    // console.log('mockConf=======>', mockConf);

    let path = mockConf.url;
    let method = mockConf.method;
    let handler = mockConf.response;

    let route = { path, method: method.toLowerCase(), handler };

    if (!mockRouteMap[method]) {
      mockRouteMap[method] = [];
    }
    console.log("create mock api: ", route.method, route.path);

    mockRouteMap[method].push(route);
  });
  return mockRouteMap;
}

// 匹配路由，命中则直接返回命中路由

function matchRoute(routes, req) {
  let path = req.url;
  let method = req.method.toLowerCase();

  let routeMethodList = routes[method];

  // console.log("method=======>", method, routeMethodList, path)

  return routeMethodList && routeMethodList.find((ele) => path === ele.path);
}

// 复写res.send方法（vite的服务使用的是connect，res并没有send方法）
function send(body) {
  let chunk = JSON.stringify(body);

  // Content-Length
  if (chunk) {
    chunk = Buffer.from(chunk, "utf-8");
    this.setHeader("Content-Length", chunk.length);
  }
  // content-type
  this.setHeader("Content-Type", "application/json");
  // status
  this.statusCode = 200;
  // respond
  this.end(chunk, "utf8");
}

export default function mockServer(options = {}) {
  options.entry = options.entry || "./mock/index.js";

  // 转绝对路径
  if (!path.isAbsolute(options.entry)) {
    options.entry = path.resolve(process.cwd(), options.entry);
  }

  // console.log("options.entry======>", options.entry);

  return {
    configureServer({ app }) {
      const mockObj = require(options.entry);

      // console.log("mockObj======>", mockObj[0]);

      let routes = createRoute(mockObj);

      // console.log("routes======>", routes);

      let middleware = (req, res, next) => {
        let route = matchRoute(routes, req);

        console.log("route========>", route);

        if (route) {
          res.send = send;
          route.handler(req, res);
        } else {
          next();
        }
      };

      app.use(middleware);
    }
  };
}
